Get Unit Skillset Ability Data
Jump to navigation
Jump to search
# ROUTINE: Get Unit Skillset Ability Data # Returns ability data for a specified unit and skillset into a handful of output lists (parallel arrays) and returns the number of abilities. # Parameters: # r4 = (unitIndex) In-battle unit index # r5 = (skillsetID) Skillset ID # r6 = (abilityIDList) Output list (Ability ID) # r7 = (abilityMPCostList) Output list (Ability MP Cost) # *(sp + 0x10) = (abilityCTList) Output list (Ability CT) # *(sp + 0x14) = (unusedOption) Unused value (never referenced) (Calling routines always pass 0 or 1) # *(sp + 0x18) = (abilityFlags) Output list (Ability Flags - Silence and persevere?) # *(sp + 0x1c) = (abilityTurns) Output list (Ability Turns - Number of turns until ability goes off) # Returns: # r2 = Number of abilities for unit in skillset? 801817c0: 27bdfed0 addiu r29,r29,-0x0130 801817c4: afa400b0 sw r4,0x00b0(r29) # unitIndex 801817c8: 8fa400b0 lw r4,0x00b0(r29) 801817cc: afb40118 sw r20,0x0118(r29) 801817d0: 8fb40140 lw r20,0x0140(r29) # abilityCTList 801817d4: afb20110 sw r18,0x0110(r29) 801817d8: 8fb20148 lw r18,0x0148(r29) # abilityFlags 801817dc: afb1010c sw r17,0x010c(r29) 801817e0: 8fb1014c lw r17,0x014c(r29) # abilityTurns 801817e4: afbe0128 sw r30,0x0128(r29) 801817e8: 0000f021 addu r30,r0,r0 # abilityIndex = 0 801817ec: afbf012c sw r31,0x012c(r29) 801817f0: afb70124 sw r23,0x0124(r29) 801817f4: afb60120 sw r22,0x0120(r29) 801817f8: afb5011c sw r21,0x011c(r29) 801817fc: afb30114 sw r19,0x0114(r29) 80181800: afb00108 sw r16,0x0108(r29) 80181804: afa600c0 sw r6,0x00c0(r29) # &abilityIDList[0] 80181808: afa000e0 sw r0,0x00e0(r29) # hasMateriaBladeEquipped = false 8018180c: afa000e8 sw r0,0x00e8(r29) # hasSwordEquipped = false 80181810: afa000f0 sw r0,0x00f0(r29) # chargeValue = 0 // 2 = Non-charge, 1 = Short Charge, 0 = neither 80181814: afa000f8 sw r0,0x00f8(r29) # isHalfMP = false 80181818: afa00100 sw r0,0x0100(r29) # isFrog = false 8018181c: afa700c8 sw r7,0x00c8(r29) # abilityMPCostList 80181820: 0c060435 jal 0x801810d4 # unit = Get Existent Battle Unit Pointer (unitIndex); 80181824: a3a500b8 sb r5,0x00b8(r29) # skillsetID 80181828: 00408021 addu r16,r2,r0 # unit 8018182c: 120000c3 beq r16,r0,0x80181b3c # if (unit == null) return 0; 80181830: 00001021 addu r2,r0,r0 80181834: 9202005a lbu r2,0x005a(r16) # unit.CurrentStatuses3 80181838: 00000000 nop 8018183c: 30420002 andi r2,r2,0x0002 80181840: 10400003 beq r2,r0,0x80181850 # if (unit.CurrentStatuses3 & STATUS_FROG) { 80181844: 00000000 nop 80181848: 34090001 ori r9,r0,0x0001 8018184c: afa90100 sw r9,0x0100(r29) # isFrog = true # } 80181850: 92020090 lbu r2,0x0090(r16) # unit.Support2 80181854: 00000000 nop 80181858: 30420080 andi r2,r2,0x0080 8018185c: 10400003 beq r2,r0,0x8018186c # if (unit.Support2 & SUPPORT_HALF_OF_MP) { 80181860: 00000000 nop 80181864: 34080001 ori r8,r0,0x0001 80181868: afa800f8 sw r8,0x00f8(r29) # isHalfMP = true # } 8018186c: 92030092 lbu r3,0x0092(r16) # unit.Support4 80181870: 00000000 nop 80181874: 30620004 andi r2,r3,0x0004 80181878: 10400003 beq r2,r0,0x80181888 8018187c: 34090002 ori r9,r0,0x0002 # if (unit.Support4 & SUPPORT_NON_CHARGE) { 80181880: 08060626 j 0x80181898 80181884: afa900f0 sw r9,0x00f0(r29) # chargeValue = 2 # } 80181888: 30620008 andi r2,r3,0x0008 8018188c: 10400002 beq r2,r0,0x80181898 # else if (unit.Support4 & SUPPORT_SHORT_CHARGE) { 80181890: 34080001 ori r8,r0,0x0001 80181894: afa800f0 sw r8,0x00f0(r29) # chargeValue = 1 # } 80181898: 27a40010 addiu r4,r29,0x0010 8018189c: 0c060dc3 jal 0x8018370c # Calculate AT List (localATList, 0); 801818a0: 00002821 addu r5,r0,r0 801818a4: 92030184 lbu r3,0x0184(r16) # unit.EquippedFlags 801818a8: 00000000 nop 801818ac: 30620004 andi r2,r3,0x0004 801818b0: 10400003 beq r2,r0,0x801818c0 801818b4: 30620008 andi r2,r3,0x0008 # if (unit.EquippedFlags & EQUIPPED_MATERIA_BLADE) { 801818b8: 34090001 ori r9,r0,0x0001 801818bc: afa900e0 sw r9,0x00e0(r29) # hasMateriaBladeEquipped = true # } 801818c0: 10400003 beq r2,r0,0x801818d0 # if (unit.EquippedFlags & EQUIPPED_SWORD) { 801818c4: 00000000 nop 801818c8: 34080001 ori r8,r0,0x0001 801818cc: afa800e8 sw r8,0x00e8(r29) # hasSwordEquipped = true # } 801818d0: 92020006 lbu r2,0x0006(r16) # unit.Flags 801818d4: 00000000 nop 801818d8: 30420020 andi r2,r2,0x0020 801818dc: 14400016 bne r2,r0,0x80181938 # if ((unit.Flags & FLAGS_MONSTER) == 0) { // If human, not monster 801818e0: 00000000 nop 801818e4: 93a900b8 lbu r9,0x00b8(r29) # skillsetID 801818e8: 00000000 nop 801818ec: 2522fffb addiu r2,r9,-0x0005 # skillsetID - 5 801818f0: 304200ff andi r2,r2,0x00ff 801818f4: 2c420013 sltiu r2,r2,0x0013 801818f8: 10400004 beq r2,r0,0x8018190c # if ((skillsetID - 5) < 0x13) { // If skillset ID is between 0x05 and 0x17, inclusive (generic skillset, excluding Mime) 801818fc: 00000000 nop 80181900: 93a200b8 lbu r2,0x00b8(r29) # skillsetID 80181904: 0806064f j 0x8018193c 80181908: 2445fffb addiu r5,r2,-0x0005 # unitSkillsetIndex = skillsetID - 5 # } else { 8018190c: 92020012 lbu r2,0x0012(r16) # unit.PrimarySkillset 80181910: 93a300b8 lbu r3,0x00b8(r29) # skillsetID 80181914: 00000000 nop 80181918: 10620005 beq r3,r2,0x80181930 8018191c: 00002821 addu r5,r0,r0 # unitSkillsetIndex = 0 # if (skillsetID != unit.PrimarySkillset) { 80181920: 92020162 lbu r2,0x0162(r16) # unit.SpecialSkillset 80181924: 00000000 nop 80181928: 14620003 bne r3,r2,0x80181938 # if (skillsetID != unit.SpecialSkillset) 8018192c: 00000000 nop # unitSkillsetIndex = -1 # } 80181930: 08060650 j 0x80181940 80181934: 2402ffff addiu r2,r0,-0x0001 # } # } else { 80181938: 2405ffff addiu r5,r0,-0x0001 # unitSkillsetIndex = -1 8018193c: 2402ffff addiu r2,r0,-0x0001 # } 80181940: 14a20004 bne r5,r2,0x80181954 # if (unitSkillsetIndex == -1) { 80181944: 3c0800ff lui r8,0x00ff # // Either ((unit is a monster) 80181948: 3508ffff ori r8,r8,0xffff # // or (skillsetID is not between 0x05 and 0x18 and not set as the primary or special skillset))... 8018194c: 08060658 j 0x80181960 80181950: afa800d0 sw r8,0x00d0(r29) # knownAbilityFlags = 0xffffff // All abilities learned # } else { 80181954: 0c017880 jal 0x8005e200 80181958: 02002021 addu r4,r16,r0 8018195c: afa200d0 sw r2,0x00d0(r29) # knownAbilityFlags = Get Known Abilities (unit, unitSkillsetIndex); # } 80181960: 00009821 addu r19,r0,r0 # abilitySlotIndex = 0 80181964: 03d1b821 addu r23,r30,r17 # abilityTurns[abilitySlotIndex] 80181968: 03d2b021 addu r22,r30,r18 # abilityFlags[abilitySlotIndex] 8018196c: 8fa900c8 lw r9,0x00c8(r29) # abilityMPCostList 80181970: 03d4a821 addu r21,r30,r20 # abilityCTList[abilitySlotIndex] 80181974: 03c9a021 addu r20,r30,r9 # abilityMPCostList[abilitySlotIndex] 80181978: 3c020080 lui r2,0x0080 # for (; abilitySlotIndex < 16; abilitySlotIndex++) { 8018197c: 8fa800d0 lw r8,0x00d0(r29) # knownAbilityFlags 80181980: 02621007 srav r2,r2,r19 # 0x800000 >> abilitySlotIndex 80181984: 01021024 and r2,r8,r2 80181988: 10400064 beq r2,r0,0x80181b1c # if ((knownAbilityFlags & (0x800000 >> abilitySlotIndex)) == 0) continue; 8018198c: 00000000 nop 80181990: 93a400b8 lbu r4,0x00b8(r29) 80181994: 0c01695a jal 0x8005a568 # abilityID = Get Ability ID From Skillset (skillsetID, abilitySlotIndex); 80181998: 02602821 addu r5,r19,r0 8018199c: 8fa90100 lw r9,0x0100(r29) # isFrog 801819a0: 00402021 addu r4,r2,r0 # abilityID 801819a4: 11200006 beq r9,r0,0x801819c0 801819a8: a7a400d8 sh r4,0x00d8(r29) # abilityID # if (isFrog) { 801819ac: 00041400 sll r2,r4,0x10 801819b0: 00021403 sra r2,r2,0x10 # abilityID 801819b4: 3403001d ori r3,r0,0x001d 801819b8: 14430058 bne r2,r3,0x80181b1c # if (abilityID != 0x1d) continue; // Frog 801819bc: 00000000 nop # } 801819c0: 00041400 sll r2,r4,0x10 801819c4: 00021c03 sra r3,r2,0x10 # abilityID 801819c8: 10600054 beq r3,r0,0x80181b1c # if (abilityID == 0) continue; 801819cc: 2482ffff addiu r2,r4,-0x0001 # abilityID - 1 801819d0: 3042ffff andi r2,r2,0xffff 801819d4: 2c42016f sltiu r2,r2,0x016f 801819d8: 10400036 beq r2,r0,0x80181ab4 # if ((abilityID - 1) < 0x016f) { // Ability ID is in range [1, 0x16f] - Normal ability, not Attack 801819dc: 000310c0 sll r2,r3,0x03 801819e0: 00431023 subu r2,r2,r3 801819e4: 00021040 sll r2,r2,0x01 801819e8: 3c038006 lui r3,0x8006 801819ec: 2463fbf0 addiu r3,r3,-0x0410 801819f0: 00432021 addu r4,r2,r3 # abilityData[abilityID] 801819f4: 90830006 lbu r3,0x0006(r4) # abilityData[abilityID].Flags4 801819f8: 00000000 nop 801819fc: 30620008 andi r2,r3,0x0008 80181a00: 10400005 beq r2,r0,0x80181a18 # if (abilityData[abilityID].Flags4 & FLAGS_REQUIRES_SWORD) { 80181a04: 00000000 nop 80181a08: 8fa800e8 lw r8,0x00e8(r29) # hasSwordEquipped 80181a0c: 00000000 nop 80181a10: 11000042 beq r8,r0,0x80181b1c # if (!hasSwordEquipped) continue; 80181a14: 00000000 nop # } 80181a18: 30620004 andi r2,r3,0x0004 80181a1c: 10400005 beq r2,r0,0x80181a34 # if (abilityData[abilityID].Flags4 & FLAGS_REQUIRES_MATERIA_BLADE) { 80181a20: 00000000 nop 80181a24: 8fa900e0 lw r9,0x00e0(r29) # hasMateriaBladeEquipped 80181a28: 00000000 nop 80181a2c: 1120003b beq r9,r0,0x80181b1c # if (!hasMateriaBladeEquipped) continue; 80181a30: 00000000 nop # } 80181a34: 8fa800f8 lw r8,0x00f8(r29) # isHalfMP 80181a38: 9091000d lbu r17,0x000d(r4) # MPCost = abilityData[abilityID].MPCost 80181a3c: 11000002 beq r8,r0,0x80181a48 80181a40: 26220001 addiu r2,r17,0x0001 # abilityData[abilityID].MPCost + 1 # if (isHalfMP) { 80181a44: 00028843 sra r17,r2,0x01 # MPCost = (abilityData[abilityID].MPCost + 1) / 2 # } 80181a48: 9082000c lbu r2,0x000c(r4) # abilityData[abilityID].CT 80181a4c: 90830005 lbu r3,0x0005(r4) # abilityData[abilityID].Flags3 80181a50: 3050007f andi r16,r2,0x007f # CT = abilityData[abilityID].CT & 0x7f 80181a54: 000321c2 srl r4,r3,0x07 # isReflectable = abilityData[abilityID].Flags3 >> 7 // (0x01 or 0x00) 80181a58: 30620020 andi r2,r3,0x0020 # abilityData[abilityID].Flags3 & FLAGS_AFFECTED_BY_SILENCE 80181a5c: 00021102 srl r2,r2,0x04 # isAffectedBySilence = (abilityData[abilityID].Flags3 & FLAGS_AFFECTED_BY_SILENCE) >> 4 // (0x02 or 0x00) 80181a60: 30630004 andi r3,r3,0x0004 # abilityData[abilityID].Flags3 & FLAGS_PERFORMING 80181a64: 1460000b bne r3,r0,0x80181a94 80181a68: 00829025 or r18,r4,r2 # flags = isReflectable | isAffectedBySilence # if ((abilityData[abilityID].Flags3 & FLAGS_PERFORMING) == 0) { 80181a6c: 8fa900f0 lw r9,0x00f0(r29) # chargeValue 80181a70: 34020001 ori r2,r0,0x0001 80181a74: 15220002 bne r9,r2,0x80181a80 # if (chargeValue == 1) { // Short Charge 80181a78: 26020001 addiu r2,r16,0x0001 # CT + 1 80181a7c: 00028043 sra r16,r2,0x01 # CT = (CT + 1) / 2 # } 80181a80: 8fa800f0 lw r8,0x00f0(r29) # chargeValue 80181a84: 34020002 ori r2,r0,0x0002 80181a88: 15020003 bne r8,r2,0x80181a98 80181a8c: 02002821 addu r5,r16,r0 # if (chargeValue == 2) { // Non-charge 80181a90: 00008021 addu r16,r0,r0 # CT = 0 # } # } 80181a94: 02002821 addu r5,r16,r0 80181a98: 8fa400b0 lw r4,0x00b0(r29) 80181a9c: 0c0605c8 jal 0x80181720 # numTurns = Get Number of Turns To Resolve (unitIndex, CT, localATList); 80181aa0: 27a60010 addiu r6,r29,0x0010 80181aa4: a2910000 sb r17,0x0000(r20) # abilityMPCostList[abilityIndex] = MPCost 80181aa8: a2b00000 sb r16,0x0000(r21) # abilityCTList[abilityIndex] = CT 80181aac: 080606bc j 0x80181af0 80181ab0: a2d20000 sb r18,0x0000(r22) # abilityFlags[abilityIndex] = flags; abilityTurns[abilityIndex] = numTurns; # } else { 80181ab4: 2482fe6a addiu r2,r4,-0x0196 80181ab8: 3042ffff andi r2,r2,0xffff 80181abc: 2c420008 sltiu r2,r2,0x0008 80181ac0: 1040000c beq r2,r0,0x80181af4 # if ((abilityID - 0x0196) < 8) { // 0x0x196 to 0x019D - Charge abilities 80181ac4: 00031040 sll r2,r3,0x01 80181ac8: 27a60010 addiu r6,r29,0x0010 80181acc: 3c018006 lui r1,0x8006 80181ad0: 00220821 addu r1,r1,r2 80181ad4: 90300d18 lbu r16,0x0d18(r1) # CT = chargeAbilityData[abilityID - 0x0196].CT 80181ad8: 8fa400b0 lw r4,0x00b0(r29) 80181adc: 0c0605c8 jal 0x80181720 # numTurns = Get Number of Turns To Resolve (unitIndex, CT, localATList); 80181ae0: 02002821 addu r5,r16,r0 80181ae4: a2800000 sb r0,0x0000(r20) # abilityMPCostList[abilityIndex] = 0 80181ae8: a2b00000 sb r16,0x0000(r21) # abilityCTList[abilityIndex] = CT 80181aec: a2c00000 sb r0,0x0000(r22) # abilityFlags[abilityIndex] = 0 80181af0: a2e20000 sb r2,0x0000(r23) # abilityTurns[abilityIndex] = numTurns # } # } 80181af4: 26f70001 addiu r23,r23,0x0001 # (abilityTurns[abilityIndex]) 80181af8: 26d60001 addiu r22,r22,0x0001 # (abilityFlags[abilityIndex]) 80181afc: 26b50001 addiu r21,r21,0x0001 # (abilityCTList[abilityIndex]) 80181b00: 26940001 addiu r20,r20,0x0001 # (abilityMPCostList[abilityIndex]) 80181b04: 97a800d8 lhu r8,0x00d8(r29) # abilityID 80181b08: 8fa900c0 lw r9,0x00c0(r29) # storeAbilityPtr = &abilityIDList[abilityIndex] 80181b0c: 27de0001 addiu r30,r30,0x0001 # abilityIndex = abilityIndex + 1 80181b10: a5280000 sh r8,0x0000(r9) # *storeAbilityPtr = abilityID 80181b14: 25290002 addiu r9,r9,0x0002 80181b18: afa900c0 sw r9,0x00c0(r29) # &abilityIDList[abilityIndex] 80181b1c: 26730001 addiu r19,r19,0x0001 # // (abilitySlotIndex = abilitySlotIndex + 1) 80181b20: 2a620010 slti r2,r19,0x0010 80181b24: 1440ff95 bne r2,r0,0x8018197c 80181b28: 3c020080 lui r2,0x0080 # } 80181b2c: 8fa900c0 lw r9,0x00c0(r29) # &abilityIDList[abilityIndex] 80181b30: 2402ffff addiu r2,r0,-0x0001 80181b34: a5220000 sh r2,0x0000(r9) # abilityIDList[abilityIndex] = -1 80181b38: 03c01021 addu r2,r30,r0 # return abilityIndex; 80181b3c: 8fbf012c lw r31,0x012c(r29) 80181b40: 8fbe0128 lw r30,0x0128(r29) 80181b44: 8fb70124 lw r23,0x0124(r29) 80181b48: 8fb60120 lw r22,0x0120(r29) 80181b4c: 8fb5011c lw r21,0x011c(r29) 80181b50: 8fb40118 lw r20,0x0118(r29) 80181b54: 8fb30114 lw r19,0x0114(r29) 80181b58: 8fb20110 lw r18,0x0110(r29) 80181b5c: 8fb1010c lw r17,0x010c(r29) 80181b60: 8fb00108 lw r16,0x0108(r29) 80181b64: 27bd0130 addiu r29,r29,0x0130 80181b68: 03e00008 jr r31 80181b6c: 00000000 nop