From 49937a640bd2c7f6c57ff0f4f69271a1e3bea8cb Mon Sep 17 00:00:00 2001 From: magumagu9 Date: Tue, 10 Feb 2009 13:11:32 +0000 Subject: [PATCH] JitIL: Make selectively disabling JIT instructions from the debugger work correctly. git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@2205 8ced0084-cf51-0410-be5f-012b33b47a6e --- Source/Core/Core/Src/PowerPC/Jit64IL/Jit.cpp | 8 ------ Source/Core/Core/Src/PowerPC/Jit64IL/Jit.h | 5 ++++ .../Src/PowerPC/Jit64IL/Jit_FloatingPoint.cpp | 4 +++ .../Core/Src/PowerPC/Jit64IL/Jit_Integer.cpp | 28 +++++++++++++++++++ .../Src/PowerPC/Jit64IL/Jit_LoadStore.cpp | 9 +++++- .../PowerPC/Jit64IL/Jit_LoadStoreFloating.cpp | 6 ++++ .../PowerPC/Jit64IL/Jit_LoadStorePaired.cpp | 2 ++ .../Core/Src/PowerPC/Jit64IL/Jit_Paired.cpp | 11 +++++++- .../PowerPC/Jit64IL/Jit_SystemRegisters.cpp | 6 ++-- 9 files changed, 67 insertions(+), 12 deletions(-) diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.cpp index 8459b70e60..7ebe8ea619 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.cpp @@ -395,14 +395,6 @@ namespace CPUCompare const u8* Jit64::DoJit(u32 em_address, PPCAnalyst::CodeBuffer *code_buffer, JitBlock *b) { - Core::g_CoreStartupParameter.bJITLoadStoreOff = true; - Core::g_CoreStartupParameter.bJITLoadStoreFloatingOff = true; - Core::g_CoreStartupParameter.bJITLoadStorePairedOff = true; - Core::g_CoreStartupParameter.bJITFloatingPointOff = true; - Core::g_CoreStartupParameter.bJITIntegerOff = true; - Core::g_CoreStartupParameter.bJITPairedOff = true; - Core::g_CoreStartupParameter.bJITSystemRegistersOff = true; - Core::g_CoreStartupParameter.bJITBranchOff = true; if (em_address == 0) PanicAlert("ERROR : Trying to compile at 0. LR=%08x", LR); diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.h b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.h index e98922b83a..8d7c48b771 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.h +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit.h @@ -62,6 +62,11 @@ struct CONTEXT // #define INSTRUCTION_START PPCTables::CountInstruction(inst); #define INSTRUCTION_START +#define JITDISABLE(type) \ + if (Core::g_CoreStartupParameter.bJITOff || \ + Core::g_CoreStartupParameter.bJIT##type##Off) \ + {Default(inst); return;} + class TrampolineCache : public Gen::XCodeBlock { public: diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_FloatingPoint.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_FloatingPoint.cpp index 71faca31fc..f0bbae1437 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_FloatingPoint.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_FloatingPoint.cpp @@ -32,6 +32,7 @@ void Jit64::fp_arith_s(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(FloatingPoint) if (inst.Rc || (inst.SUBOP5 != 25 && inst.SUBOP5 != 20 && inst.SUBOP5 != 21)) { Default(inst); return; } @@ -66,6 +67,7 @@ void Jit64::fmaddXX(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(FloatingPoint) if (inst.Rc) { Default(inst); return; } @@ -90,6 +92,7 @@ void Jit64::fmrx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(FloatingPoint) if (inst.Rc) { Default(inst); return; } @@ -101,6 +104,7 @@ void Jit64::fcmpx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(FloatingPoint) IREmitter::InstLoc lhs, rhs, res; lhs = ibuild.EmitLoadFReg(inst.FA); rhs = ibuild.EmitLoadFReg(inst.FB); diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Integer.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Integer.cpp index c49187eff0..ecd8851211 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Integer.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Integer.cpp @@ -42,6 +42,7 @@ void Jit64::reg_imm(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) int d = inst.RD, a = inst.RA, s = inst.RS; IREmitter::InstLoc val, test, c; switch (inst.OPCD) @@ -109,6 +110,7 @@ void Jit64::cmpXX(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc lhs, rhs, res; lhs = ibuild.EmitLoadGReg(inst.RA); if (inst.OPCD == 31) { @@ -132,6 +134,7 @@ void Jit64::orx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RB); val = ibuild.EmitOr(ibuild.EmitLoadGReg(inst.RS), val); ibuild.EmitStoreGReg(val, inst.RA); @@ -144,6 +147,7 @@ void Jit64::xorx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RB); val = ibuild.EmitXor(ibuild.EmitLoadGReg(inst.RS), val); ibuild.EmitStoreGReg(val, inst.RA); @@ -154,6 +158,7 @@ void Jit64::andx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RB); val = ibuild.EmitAnd(ibuild.EmitLoadGReg(inst.RS), val); ibuild.EmitStoreGReg(val, inst.RA); @@ -164,6 +169,7 @@ void Jit64::extsbx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS); val = ibuild.EmitSExt8(val); ibuild.EmitStoreGReg(val, inst.RA); @@ -174,6 +180,7 @@ void Jit64::extshx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS); val = ibuild.EmitSExt16(val); ibuild.EmitStoreGReg(val, inst.RA); @@ -183,6 +190,8 @@ void Jit64::subfic(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc nota, lhs, val, test; nota = ibuild.EmitXor(ibuild.EmitLoadGReg(inst.RA), ibuild.EmitIntConst(-1)); @@ -200,6 +209,8 @@ void Jit64::subfcx(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Integer) if (inst.OE) PanicAlert("OE: subfcx"); IREmitter::InstLoc val, test, lhs, rhs; lhs = ibuild.EmitLoadGReg(inst.RB); @@ -215,6 +226,8 @@ void Jit64::subfex(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Integer) if (inst.OE) PanicAlert("OE: subfex"); IREmitter::InstLoc val, test, lhs, rhs, carry; rhs = ibuild.EmitLoadGReg(inst.RA); @@ -235,6 +248,7 @@ void Jit64::subfx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) if (inst.OE) PanicAlert("OE: subfx"); IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RB); val = ibuild.EmitSub(val, ibuild.EmitLoadGReg(inst.RA)); @@ -246,6 +260,7 @@ void Jit64::mulli(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RA); val = ibuild.EmitMul(val, ibuild.EmitIntConst(inst.SIMM_16)); ibuild.EmitStoreGReg(val, inst.RD); @@ -254,6 +269,7 @@ void Jit64::mullwx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RB); val = ibuild.EmitMul(ibuild.EmitLoadGReg(inst.RA), val); ibuild.EmitStoreGReg(val, inst.RD); @@ -332,6 +348,7 @@ void Jit64::addx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RB); val = ibuild.EmitAdd(ibuild.EmitLoadGReg(inst.RA), val); ibuild.EmitStoreGReg(val, inst.RD); @@ -342,6 +359,7 @@ void Jit64::addzex(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc lhs = ibuild.EmitLoadGReg(inst.RA), val, newcarry; val = ibuild.EmitAdd(lhs, ibuild.EmitLoadCarry()); @@ -386,6 +404,7 @@ void Jit64::rlwinmx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) unsigned mask = Helper_Mask(inst.MB, inst.ME); IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS); val = ibuild.EmitRol(val, ibuild.EmitIntConst(inst.SH)); @@ -399,6 +418,7 @@ void Jit64::rlwimix(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) unsigned mask = Helper_Mask(inst.MB, inst.ME); IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS); val = ibuild.EmitRol(val, ibuild.EmitIntConst(inst.SH)); @@ -414,6 +434,7 @@ void Jit64::rlwnmx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) unsigned int mask = Helper_Mask(inst.MB, inst.ME); IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS); val = ibuild.EmitRol(val, ibuild.EmitLoadGReg(inst.RB)); @@ -426,6 +447,7 @@ void Jit64::negx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RA); val = ibuild.EmitSub(ibuild.EmitIntConst(0), val); ibuild.EmitStoreGReg(val, inst.RD); @@ -436,6 +458,7 @@ void Jit64::srwx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS), samt = ibuild.EmitLoadGReg(inst.RB), corr; @@ -454,6 +477,7 @@ void Jit64::slwx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS), samt = ibuild.EmitLoadGReg(inst.RB), corr; @@ -472,6 +496,7 @@ void Jit64::srawx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) // FIXME: We can do a lot better on 64-bit IREmitter::InstLoc val, samt, mask, mask2, test; val = ibuild.EmitLoadGReg(inst.RS); @@ -494,6 +519,7 @@ void Jit64::srawix(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS), test; val = ibuild.EmitSarl(val, ibuild.EmitIntConst(inst.SH)); ibuild.EmitStoreGReg(val, inst.RA); @@ -509,6 +535,8 @@ // count leading zeroes void Jit64::cntlzwx(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Integer) IREmitter::InstLoc val = ibuild.EmitLoadGReg(inst.RS); val = ibuild.EmitCntlzw(val); ibuild.EmitStoreGReg(val, inst.RA); diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStore.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStore.cpp index d7ed89aa3f..0ee939f981 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStore.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStore.cpp @@ -42,6 +42,7 @@ void Jit64::lhax(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitLoadGReg(inst.RB); if (inst.RA) addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); @@ -53,7 +54,7 @@ void Jit64::lhax(UGeckoInstruction inst) void Jit64::lXz(UGeckoInstruction inst) { INSTRUCTION_START - + JITDISABLE(LoadStore) if (Core::GetStartupParameter().bSkipIdle && inst.OPCD == 32 && (inst.hex & 0xFFFF0000) == 0x800D0000 && @@ -86,6 +87,7 @@ void Jit64::lXz(UGeckoInstruction inst) void Jit64::lha(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitIntConst((s32)(s16)inst.SIMM_16); if (inst.RA) @@ -98,6 +100,7 @@ void Jit64::lha(UGeckoInstruction inst) void Jit64::lXzx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitLoadGReg(inst.RB); if (inst.RA) { addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); @@ -142,6 +145,7 @@ void Jit64::dcbz(UGeckoInstruction inst) void Jit64::stX(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16), value = ibuild.EmitLoadGReg(inst.RS); if (inst.RA) @@ -160,6 +164,7 @@ void Jit64::stX(UGeckoInstruction inst) void Jit64::stXx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitLoadGReg(inst.RB), value = ibuild.EmitLoadGReg(inst.RS); addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); @@ -178,6 +183,7 @@ void Jit64::stXx(UGeckoInstruction inst) void Jit64::lmw(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16); if (inst.RA) addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); @@ -192,6 +198,7 @@ void Jit64::lmw(UGeckoInstruction inst) void Jit64::stmw(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStore) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16); if (inst.RA) addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStoreFloating.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStoreFloating.cpp index 4a6f5ed783..b0704ed450 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStoreFloating.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStoreFloating.cpp @@ -46,6 +46,7 @@ void Jit64::lfs(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStoreFloating) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16), val; if (inst.RA) addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); @@ -58,6 +59,7 @@ void Jit64::lfs(UGeckoInstruction inst) void Jit64::lfd(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStoreFloating) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16), val; if (inst.RA) addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); @@ -71,6 +73,7 @@ void Jit64::lfd(UGeckoInstruction inst) void Jit64::stfd(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStoreFloating) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16), val = ibuild.EmitLoadFReg(inst.RS); if (inst.RA) @@ -85,6 +88,7 @@ void Jit64::stfd(UGeckoInstruction inst) void Jit64::stfs(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStoreFloating) IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_16), val = ibuild.EmitLoadFReg(inst.RS); if (inst.RA) @@ -100,6 +104,7 @@ void Jit64::stfs(UGeckoInstruction inst) void Jit64::stfsx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStoreFloating) IREmitter::InstLoc addr = ibuild.EmitLoadGReg(inst.RB), val = ibuild.EmitLoadFReg(inst.RS); if (inst.RA) @@ -113,6 +118,7 @@ void Jit64::stfsx(UGeckoInstruction inst) void Jit64::lfsx(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStoreFloating) IREmitter::InstLoc addr = ibuild.EmitLoadGReg(inst.RB), val; if (inst.RA) addr = ibuild.EmitAdd(addr, ibuild.EmitLoadGReg(inst.RA)); diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStorePaired.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStorePaired.cpp index 38257a76d7..9d6b37cd54 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStorePaired.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_LoadStorePaired.cpp @@ -45,6 +45,7 @@ void Jit64::psq_st(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStorePaired) if (inst.W) {Default(inst); return;} IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_12), val; if (inst.RA) @@ -59,6 +60,7 @@ void Jit64::psq_st(UGeckoInstruction inst) void Jit64::psq_l(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(LoadStorePaired) if (inst.W) {Default(inst); return;} IREmitter::InstLoc addr = ibuild.EmitIntConst(inst.SIMM_12), val; if (inst.RA) diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Paired.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Paired.cpp index ddc6a5b53b..edaabad95d 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Paired.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_Paired.cpp @@ -49,6 +49,8 @@ void Jit64::ps_arith(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Paired) if (inst.Rc || (inst.SUBOP5 != 21 && inst.SUBOP5 != 20 && inst.SUBOP5 != 25)) { Default(inst); return; } @@ -78,7 +80,8 @@ { // FIXME: This operation strikes me as a bit strange... // perhaps we can optimize it depending on the users? - INSTRUCTION_START; + INSTRUCTION_START + JITDISABLE(Paired) if (inst.Rc || inst.SUBOP5 != 10) { Default(inst); return; } @@ -96,6 +99,8 @@ void Jit64::ps_muls(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Paired) if (inst.Rc) { Default(inst); return; } @@ -119,6 +124,8 @@ //TODO: find easy cases and optimize them, do a breakout like ps_arith void Jit64::ps_mergeXX(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Paired) if (inst.Rc) { Default(inst); return; } @@ -150,6 +157,8 @@ void Jit64::ps_maddXX(UGeckoInstruction inst) { + INSTRUCTION_START + JITDISABLE(Paired) if (inst.Rc) { Default(inst); return; } diff --git a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_SystemRegisters.cpp b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_SystemRegisters.cpp index 431ac625c1..7fe624d00f 100644 --- a/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_SystemRegisters.cpp +++ b/Source/Core/Core/Src/PowerPC/Jit64IL/Jit_SystemRegisters.cpp @@ -36,6 +36,7 @@ void Jit64::mtspr(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(SystemRegisters) u32 iIndex = (inst.SPRU << 5) | (inst.SPRL & 0x1F); switch(iIndex) { case SPR_LR: @@ -53,6 +54,7 @@ void Jit64::mfspr(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(SystemRegisters) u32 iIndex = (inst.SPRU << 5) | (inst.SPRL & 0x1F); switch (iIndex) { @@ -83,14 +85,14 @@ void Jit64::mfmsr(UGeckoInstruction inst) { INSTRUCTION_START + JITDISABLE(SystemRegisters) ibuild.EmitStoreGReg(ibuild.EmitLoadMSR(), inst.RD); } void Jit64::mftb(UGeckoInstruction inst) { - if(Core::g_CoreStartupParameter.bJITOff || Core::g_CoreStartupParameter.bJITSystemRegistersOff) - {Default(inst); return;} // turn off from debugger INSTRUCTION_START; + JITDISABLE(SystemRegisters) mfspr(inst); }