///////////////////////////////////////////////////////////////////////////////// // // Persona 2 Eternal Punishment (PSX) JAP / Custom Strings Concatination // Author: Sergey Shemet 31/01/2026 // // input: // a0 - destination address // a1 - source address // // free registers: // v0,v1,a2,a3 concat_string: lhu v0, 0x0(a0) //if string is initializated as empty move a3, a0 //a3 dest address copy for header update srl v1, v0, 0x0D bne v1, zero, init_counter nop li v1,0x2000 sh v1,0x0(a0) clear a2 //a2 - char counter for saving in string header j string_copy_start nop init_counter: andi a2, v0, 0xFF //clear command, only length addu a0, a0, a2 // dest addr a0 ready for save // a2 - actual char counter string_copy_start: lhu v0, 0x0(a1) //checking source format addiu a0, 0x2 //shift destination address over header srl v1, v0, 0x0D beq v1, zero, japanese_text_src nop russian_text_src: andi v1, v0, 0xFF //v1 is src char counter move a2, v1 //cntr for header update addiu a1, 2 //shift src address for russian string russian_char_loop: lbu v0, 0x0(a1) addiu v1, -0x1 sb v0, 0x0(a0) beq v1, 0, update_header addiu a0, 0x1 //simple bytecopy loop with counter dec... j russian_char_loop addiu a1, 0x1 japanese_text_src: lhu v0, 0x0(a1) nop srl v0, v0, 0x0C //checking end command code bne v0, 0, update_header //end if jap line end nop lhu v0, 0x0(a1) //load kanji again addiu a1, 0x2 //add source address sb v0, 0x0(a0) //save first byte to dest addiu a2, 0x1 //increase char counter j japanese_text_src //looop reading addiu a0, 0x1 // ...and shift dest addr update_header: lbu v0, 0x0(a3) //load counter nop addu a2, a2, v0 //actual counter + current counter sb a2, 0x0(a3) //save jr ra nop