System(s) |
Playstation, PSP, PSN (POPS) |
Bug Type | Gameplay |
Region Introduced | |
Patch Version | 1.01.02b |
The Kindness Rune is a weapon-only rune that is intended to give a large, but limited bonus to a character's ATK. When the Rune is attached, each character may receive a bonus of up to 127 points, based on how "kind" you have been to them. Due to the implementation, it is difficult to be certain what the developers intended by allowing characters' "Kindness Ratings" to become negative. It may be intended to hold the bonus at zero for a longer time period, but it appears more likely that the rune was actually intended to subtract from ATK in this event. Regardless, the bug comes into operation when the character's rating drops below zero, and their ATK is maximized to 999.
This is one of several bugs that is actually somewhat beneficial to the player.
The rating can range from -128 to +127 and is added into the ATK value after all other bonuses have been applied.
The key to triggering the bug is by minimizing increases for a character, and allowing them to remain dead through the end of battle. When the Kindness Rating is forced into negative values, the bug comes into effect and their ATK will be set to maximum whenever the Kindness Rune is equipped to them.
Code taken from the US main executable (SLUS_009.58)
TEXT:80088950 loc_80088950: # CODE XREF: sub_80088864:loc_80088900j TEXT:80088950 bne $s0, $v0, loc_80088968 TEXT:80088954 move $a0, $0 TEXT:80088958 move $a1, $a0 TEXT:8008895C jal KindnessRating TEXT:80088960 move $a2, $s1 TEXT:80088964 move $s2, $v0 TEXT:80088968 TEXT:80088968 loc_80088968: # CODE XREF: sub_80088864+94j TEXT:80088968 # sub_80088864+E4j ... TEXT:80088968 lhu $v0, 0x38+var_28($sp) TEXT:8008896C andi $v1, $s4, 0xFFFF TEXT:80088970 addu $v0, $v1 TEXT:80088974 andi $v1, $s2, 0xFFFF <---- This is the cause of the bug. TEXT:80088978 addu $v1, $v0, $v1 TEXT:8008897C slti $v0, $v1, 0x3E8 TEXT:80088980 beqz $v0, loc_80088994 TEXT:80088984 li $v0, 0x3E7 TEXT:80088988 bltz $v1, loc_80088994 TEXT:8008898C move $v0, $0 TEXT:80088990 andi $v0, $v1, 0xFFFF
The indicated line is the source of the problem. If, for example, the Kindness Rating is -1, the management routine will retrieve a byte from memory as a signed value. When dealing with byte, 0xFF is -1. Since the Playstation works on 32-bit registers, the sign bit must be propagated to the unused bits of the register to preserve the value. That means that what the $s2 register contains is actually 0xFFFFFFFF. The problem operation does a bitwise AND with 0xFFFF. This will retain the least significant 16-bits and clear the high-order bits. After this operation, $s2 will contain 0x0000FFFF. This is 65,535, and not -1. This enormous value is added into the running total by the following line, and the remainder of the lines shown simply enforce bounds of 0 and 999 for the final results.